package com.docted.design.pattern.proxy.dynamic.jdk;

import sun.misc.ProxyGenerator;

import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

/**
 * @author DoCted
 * @since v1.0 2018/3/11
 */
public class JdkProxyTest {


    public static void main(String[] args) {

        DoCted doCted = new DoCted();

        Graduate graduate = (Graduate) new JobAgent().getInstance(doCted);

        graduate.findJob();
        System.out.println("-----------------------");
        Graduate graduate1 = (Graduate) new HouseAgent().getInstance(doCted);
        graduate1.rentApartment();


        /**
         * 原理：
         *  1.拿到被代理对象的引用，并且获取它实现的所有接口（通过反射）
         *  2.JDK Proxy类重新生成一个新的类，同时新的类要实现被代理类实现的所有接口
         *  3.动态生成Java代码，把新增的业务增加的生成
         *  4.生成Java代码并编译成.class
         *  5.再重新加载到JVM中
         * 以上过程叫做：字节码重组
         *
         *
         * JDK中的规范：
         *  只要是$符号开头的一般都是自动生成的
         *      内部类
         *
         *
         * 通过反编译工具可以查看源代码
         *  1.把字节码保存成文件
         *
         */

        byte[] bytes =ProxyGenerator.generateProxyClass("$Proxy0", new Class[]{Graduate.class});
        try {
            FileOutputStream fileOutputStream = new FileOutputStream("$Proxy0.class");
            fileOutputStream.write(bytes);
            fileOutputStream.close();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }

    }
}
